package com.warmheart.base.interceptor;

import java.util.List;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.method.HandlerMethod;
import org.springframework.web.servlet.handler.HandlerInterceptorAdapter;

import com.warmheart.base.annotation.Auth;
import com.warmheart.base.entity.Operator;
import com.warmheart.base.session.SessionLocalUtils;
import com.warmheart.base.session.SessionManager;
import com.warmheart.core.enums.ResultCode;
import com.warmheart.core.result.CommonResult;
import com.warmheart.core.util.JsonResponseUtil;

public class AuthInterceptor extends HandlerInterceptorAdapter {

    @Autowired(required = false)
    private SessionManager sessionManager;

    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {

        // 仅拦截对方法的访问，对于其他静态资源不进行拦截
        if (handler instanceof HandlerMethod) {

            HandlerMethod method = (HandlerMethod) handler;
            Auth auth = method.getMethod().getAnnotation(Auth.class);
            // 如果访问方法需要登录，则进行拦截
            if (auth != null && auth.verifyLogin()) {
                // 获取REDIS存储的用户数据
                Operator operator = sessionManager.getOperator(request);

                // 如果存储的登录信息已经丢失，则表示已经登录过期。跳转到登录页面
                if (operator == null) {
                    JsonResponseUtil.writerJsonFromObj(response, CommonResult.failed(ResultCode.UNAUTHORIZED, "登录已过期"));
                    return false;
                }
                if (StringUtils.isNotBlank(auth.permissions())) {
                    // 验证菜单权限，防止越权访问
                    List<String> menuList = operator.getLoginUser().getPermissionsList();
                    if (menuList == null || !menuList.contains(auth.permissions())) {
                        JsonResponseUtil.writerJsonFromObj(response,
                                CommonResult.failed(ResultCode.FORBIDDEN, "没有访问权限"));
                        return false;
                    }
                }
                // 存入本服务器缓存中，用于提高访问速度
                SessionLocalUtils.setOperator(operator);
                // 重新设置session失效时间
                sessionManager.resetOperator(request);
            } else {
                // 清空本地缓存
                SessionLocalUtils.removeOperator();
            }
        }
        return super.preHandle(request, response, handler);
    }
}
